package org.dallasrowing.logbook.ui.view;

import java.util.Date;
import java.util.List;

import org.dallasrowing.logbook.util.FormatUtil;
import org.dallasrowing.model.LogBookEntry;
import org.dallasrowing.model.Rower;
import org.eclipse.swt.SWT;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.Font;
import org.eclipse.swt.graphics.FontData;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Combo;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Event;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Listener;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.Text;

public class SWTSignOutWindow implements SignOutWindow {

	private Combo openEntriesCombo;
	private ComboModel<LogBookEntry> openEntries;
	private Button signOutSubmitButton;
	private Text entryStartDate;
	private Text entryCloseDate;
	private Text rowers;
	private Text boatUsed;
	private Text milesRowed;
	private Text comment;
	private Shell signOutDialog;
	private Color normalColor;
	private Color redColor;

	public void openSignOutWindow(Shell parent) {
		signOutDialog = new Shell (parent, SWT.DIALOG_TRIM | SWT.APPLICATION_MODAL );
		signOutDialog.setText ("Sign-Out...");
		signOutDialog.setLayout(new GridLayout(2, false));
		
		createSignOutElements( signOutDialog );
		signOutDialog.setDefaultButton(signOutSubmitButton);
		
		validateEnableSubmit();
		
		signOutDialog.layout(true, true);
		signOutDialog.pack();
		signOutDialog.open();
	}

	private void createSignOutElements( final Composite parent) {
		
		GridData gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING  );
		Label l = new Label(parent, SWT.NONE);
		l.setText("Select:");
		l.setLayoutData( gridData );

		setBoldFont(parent, l);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		openEntriesCombo = new Combo(parent, SWT.DROP_DOWN | SWT.READ_ONLY);
		openEntries = new ComboModel<LogBookEntry>();
		
		openEntriesCombo.addListener(SWT.Selection, new Listener() {
		
			public void handleEvent(Event event) {
				logBookEntrySelected(openEntriesCombo.getSelectionIndex());
				validateEnableSubmit();
			}
		
		});
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		l = new Label(parent, SWT.NONE);
		l.setText("Start Date:");
		l.setLayoutData( gridData );
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		entryStartDate = new Text(parent, SWT.BORDER);
		entryStartDate.setEnabled(false);
		entryStartDate.setLayoutData(gridData);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		l = new Label(parent, SWT.NONE);
		l.setText("End Date:");
		l.setLayoutData( gridData );
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		entryCloseDate = new Text(parent, SWT.BORDER);
		entryCloseDate.setEnabled(false);
		entryCloseDate.setLayoutData(gridData);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING  );
		l = new Label(parent, SWT.NONE);
		l.setText("Rowers:");
		l.setLayoutData( gridData );
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		rowers = new Text(parent, SWT.BORDER);
		rowers.setEnabled(false);
		rowers.setLayoutData(gridData);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING  );
		l = new Label(parent, SWT.NONE);
		l.setText("Boat used:");
		l.setLayoutData( gridData );
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		boatUsed = new Text(parent, SWT.BORDER);
		boatUsed.setEnabled(false);
		boatUsed.setLayoutData(gridData);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING  );
		l = new Label(parent, SWT.NONE);
		l.setText("Miles/Meters rowed:");
		l.setLayoutData( gridData );
		setBoldFont(parent, l);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		milesRowed = new Text(parent, SWT.BORDER);
		milesRowed.setLayoutData(gridData);
		milesRowed.addListener(SWT.Modify, new Listener() {
			public void handleEvent(Event event) {
				validateEnableSubmit();
			}
		});
		normalColor = milesRowed.getForeground();
		redColor = parent.getDisplay().getSystemColor(SWT.COLOR_RED);
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING  );
		l = new Label(parent, SWT.NONE);
		l.setText("Add Comment:");
		l.setLayoutData( gridData );
		
		gridData = new GridData( GridData.FILL_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING );
		comment = new Text(parent,  SWT.BORDER );
		comment.setTextLimit(500);
		comment.setLayoutData(gridData);

		gridData = new GridData( GridData.HORIZONTAL_ALIGN_CENTER );
		gridData.verticalIndent = 10;
		signOutSubmitButton = new Button( parent, SWT.PUSH);
		signOutSubmitButton.setText("Submit");
		signOutSubmitButton.setLayoutData(gridData);

		gridData = new GridData( GridData.HORIZONTAL_ALIGN_CENTER );
		gridData.verticalIndent = 10;
		Button cancelButton = new Button( parent, SWT.PUSH);
		cancelButton.setText("Cancel");
		cancelButton.setLayoutData(gridData);
		cancelButton.addListener(SWT.Selection, new Listener() {
		
			public void handleEvent(Event event) {
				parent.dispose();
			}
		
		});

	}

	private void setBoldFont(final Composite parent, Label l) {
		Font font = l.getFont();
		FontData[] fontData = font.getFontData();
		for (FontData d : fontData)
		{
			d.setStyle(SWT.BOLD);
		}
		l.setFont(new Font(parent.getDisplay(), fontData));
	}

	protected void validateEnableSubmit() {
		boolean enabled = true;
		
		if (openEntriesCombo.getSelectionIndex() == -1)
			enabled = false;
		
		if ( ! validMilesString( milesRowed.getText()))
		{
			enabled = false;
			milesRowed.setForeground(redColor);
		}
		else
		{
			milesRowed.setForeground(normalColor);
		}
		
		signOutSubmitButton.setEnabled(enabled);
		
	}

	private boolean validMilesString(String text) {
		if (text == null || "".equals(text))
			return false;
		
		try
		{
			Double.parseDouble(text);
		}
		catch (NumberFormatException e)
		{
			return false;
		}
		return true;
	}

	protected void logBookEntrySelected(int selectionIndex) {
		LogBookEntry logBookEntry = openEntries.getEntryFromIndex(selectionIndex);
		entryStartDate.setText( FormatUtil.formatDate( logBookEntry.getEntryOpenDate() ) );
		entryCloseDate.setText( FormatUtil.formatDate( new Date()) );
		boatUsed.setText( logBookEntry.getBoat().getName() );
		rowers.setText( formatRowers(logBookEntry.getRowers() ) );
		
		redraw();
	}

	private String formatRowers(List<Rower> rowers) {
		StringBuilder builder = new StringBuilder();
		for (int i=0; i< rowers.size(); i++)
		{
			if (i>0)
				builder.append("/");
			
			builder.append(rowers.get(i).getName());
		}
		return builder.toString();
	}

	public void setSubmitButtonListener(final Runnable action) {
		signOutSubmitButton.addListener(SWT.Selection, new Listener() {
		
			public void handleEvent(Event event) {
				action.run();
			}
		
		});		
	}

	public void updateOpenEntriesList(List<LogBookEntry> openEntries) {

		this.openEntries.load(openEntries);
		
		openEntriesCombo.removeAll();
		for (LogBookEntry entry : openEntries)
		{
			openEntriesCombo.add( createEntryString(entry) );
		}
		
		redraw();
	}

	private void redraw() {
		this.signOutDialog.pack(true);
	}

	private String createEntryString(LogBookEntry entry) {
		StringBuilder builder = new StringBuilder();
		
		builder.append(entry.getBoat().getName())
		.append(":");
		
		builder.append(formatRowers(entry.getRowers()));
		
		return builder.toString();
	}

	public String getCloseEntryDate() {
		return entryCloseDate.getText();
	}

	public String getMilesRowed() {
		return milesRowed.getText();
	}

	public LogBookEntry getSelectedOpenEntry() {
		return openEntries.getEntryFromIndex(openEntriesCombo.getSelectionIndex());
	}

	public void closeWindow() {
		signOutDialog.dispose();
	}

	public String getComment() {
		return comment.getText();
		
	}

	
}
